package com.wanrue.tcc.commom;

import com.alibaba.dubbo.rpc.Invocation;
import com.alibaba.dubbo.rpc.RpcContext;
import com.alibaba.fastjson.JSON;
import com.wanrue.tcc.common.TccMethod;
import com.wanrue.tcc.context.Context;
import org.aspectj.lang.ProceedingJoinPoint;

public class DubboContextService extends DefaultContextService {

    @Override
    public Context get(Object... args) {
        String context = RpcContext.getContext().getAttachment(Constants.TRANSACTION_CONTEXT);
        if (context != null && !"".equals(context)) {
            return JSON.parseObject(context, Context.class);
        }
        return null;
    }

    @Override
    public void set(Context context, Object... args) {
        RpcContext.getContext().setAttachment(Constants.TRANSACTION_CONTEXT, JSON.toJSONString(context));
    }

    @Override
    public TccMethod method(Object obj, Object... args) {
        TccMethod method;
        if (obj != null && obj instanceof ProceedingJoinPoint) {//注解切入点
            method = defaultMethod((ProceedingJoinPoint) obj);
            Context context = this.get(null);
            method.setContext(context);
        } else {// Rpc 调用点
            com.alibaba.dubbo.rpc.Invoker invoker = (com.alibaba.dubbo.rpc.Invoker) args[0];
            Invocation invocation = (Invocation) args[1];
            Class<?> target = invoker.getInterface();
            Class<?>[] parameterTypes = invocation.getParameterTypes();
            String methodName = invocation.getMethodName();
            Object[] arguments = invocation.getArguments();
            method = new TccMethod();
            method.setMethodName(methodName);
            method.setTargetClass(target);
            method.setParameterTypes(parameterTypes);
            method.setArgs(arguments);
            Context context = this.get(null);
            method.setContext(context);
        }
        return method;
    }


}
